/**
 * This file is a part of qloudgen-rul. 
 * You can redistribute qloudgen-rul and/or modify it under the terms of the Lesser GNU General Public License version 3. 
 * qloudgen-rul is distributed WITHOUT ANY WARRANTY. 
 *
 * See the Lesser GNU General Public License for more details at http://www.gnu.org/licenses/. 
 **/
package org.qloudgen.rul.drools.kie;

import static org.drools.compiler.kie.util.CDIHelper.wireListnersAndWIHs;

import org.drools.compiler.kie.builder.impl.KieContainerImpl;
import org.drools.compiler.kie.builder.impl.KieProject;
import org.drools.compiler.kproject.models.KieSessionModelImpl;

import org.kie.api.KieServices;
import org.kie.api.KieBase;
import org.kie.api.KieBaseConfiguration;
import org.kie.api.builder.ReleaseId;
import org.kie.api.builder.KieRepository;
import org.kie.api.builder.model.KieSessionModel;
import org.kie.api.builder.model.FileLoggerModel;
import org.kie.api.logger.KieLoggers;
import org.kie.api.runtime.Environment;
import org.kie.api.runtime.KieSession;
import org.kie.api.runtime.KieSessionConfiguration;
import org.kie.api.event.KieRuntimeEventManager;
import org.kie.internal.KnowledgeBaseFactory;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

/**
 * <p>Title: Drools Implementation</p>
 * <p>Description: Wrappered jboss drools kie container implementation.</p>
 * <p>Copyright: qloudgen/rul 2014</p>
 * @author <a href="mailto:hyq.dd.sun@gmail.com">glue.3M</a>
 */
public class DroolsKieContainerImpl extends KieContainerImpl {
	/**
	 * Log output.
	 */
	private final static Logger logger = LoggerFactory.getLogger( DroolsKieContainerImpl.class );
	
	public DroolsKieContainerImpl(KieProject kProject, KieRepository kr) {
		super( kProject , kr );
	}
	
	public DroolsKieContainerImpl(KieProject kProject, KieRepository kr, ReleaseId containerReleaseId) {
		super( kProject , kr , containerReleaseId );
	}
	
    @Override
    public KieSession newKieSession(String kSessionName, Environment environment, KieSessionConfiguration conf) {
        KieSessionModelImpl kSessionModel = (KieSessionModelImpl) getKieSessionModel(kSessionName);
        if ( kSessionModel == null ) {
            logger.error("Unknown KieSession name: " + kSessionName);
            return null;
        }
        if (kSessionModel.getType() == KieSessionModel.KieSessionType.STATELESS) {
            throw new RuntimeException("Trying to create a stateful KieSession from a stateless KieSessionModel: " + kSessionName);
        }
        KieBase kBase = getKieBase( kSessionModel.getKieBaseModel().getName() );
        if ( kBase == null ) {
            logger.error("Unknown KieBase name: " + kSessionModel.getKieBaseModel().getName());
            return null;
        }
        KieSession kSession = kBase.newKieSession( conf != null ? conf : getKnowledgeSessionConfiguration(kSessionModel), environment );
        wireListnersAndWIHs(kSessionModel, kSession);

        registerLoggers(kSessionModel, kSession);

        //KieSession oldSession = kSessions.remove(kSessionName);
        //if (oldSession != null) {
        //    oldSession.dispose();
        //}
        //kSessions.put(kSessionName, kSession);

        return kSession;
    }

    private KieSessionConfiguration getKnowledgeSessionConfiguration(KieSessionModelImpl kSessionModel) {
        KieSessionConfiguration ksConf = KnowledgeBaseFactory.newKnowledgeSessionConfiguration();
        ksConf.setOption( kSessionModel.getClockType() );
        ksConf.setOption( kSessionModel.getBeliefSystem() );
        return ksConf;
    }

    private void registerLoggers(KieSessionModelImpl kSessionModel, KieRuntimeEventManager kSession) {
        KieLoggers kieLoggers = KieServices.Factory.get().getLoggers();
        if (kSessionModel.getConsoleLogger() != null) {
            kieLoggers.newConsoleLogger(kSession);
        }
        FileLoggerModel fileLogger = kSessionModel.getFileLogger();
        if (fileLogger != null) {
            if (fileLogger.isThreaded()) {
                kieLoggers.newThreadedFileLogger(kSession, fileLogger.getFile(), fileLogger.getInterval());
            } else {
                kieLoggers.newFileLogger(kSession, fileLogger.getFile());
            }
        }
    }
}